package com.hmdp;

import com.alibaba.dashscope.aigc.generation.Generation;
import com.alibaba.dashscope.aigc.generation.GenerationParam;
import com.alibaba.dashscope.aigc.generation.GenerationResult;
import com.alibaba.dashscope.app.*;
import com.alibaba.dashscope.assistants.Assistant;
import com.alibaba.dashscope.assistants.Assistants;
import com.alibaba.dashscope.common.GeneralListParam;
import com.alibaba.dashscope.common.ListResult;
import com.alibaba.dashscope.common.Message;
import com.alibaba.dashscope.common.Role;
import com.alibaba.dashscope.exception.ApiException;
import com.alibaba.dashscope.exception.InputRequiredException;
import com.alibaba.dashscope.exception.InvalidateParameter;
import com.alibaba.dashscope.exception.NoApiKeyException;
import com.alibaba.dashscope.threads.AssistantThread;
import com.alibaba.dashscope.threads.ThreadParam;
import com.alibaba.dashscope.threads.Threads;
import com.alibaba.dashscope.threads.messages.Messages;
import com.alibaba.dashscope.threads.messages.TextMessageParam;
import com.alibaba.dashscope.threads.messages.ThreadMessage;
import com.alibaba.dashscope.threads.runs.AssistantStreamMessage;
import com.alibaba.dashscope.threads.runs.RunParam;
import com.alibaba.dashscope.threads.runs.Runs;
import com.alibaba.dashscope.utils.JsonUtils;
import com.alibaba.fastjson2.JSONObject;
import io.reactivex.Flowable;

import java.util.Arrays;
import java.util.List;

public class Main {
    public static void main(String[] args) throws ApiException, NoApiKeyException, InputRequiredException, InvalidateParameter, InterruptedException {
//        assistantUsage();
        streamCall();
    }


    public static GenerationResult callWithMessage() throws ApiException, NoApiKeyException, InputRequiredException {
        Generation gen = new Generation();
        Message systemMsg = Message.builder()
                .role(Role.SYSTEM.getValue())
                .content("You are a helpful assistant.")
                .build();
        Message userMsg = Message.builder()
                .role(Role.USER.getValue())
                .content("你是谁？")
                .build();
        GenerationParam param = GenerationParam.builder()
                // 若没有配置环境变量，请用百炼API Key将下行替换为：.apiKey("sk-xxx")
                .apiKey(System.getenv("DASHSCOPE_API_KEY"))
                // 模型列表：https://help.aliyun.com/zh/model-studio/getting-started/models
                .model("qwen-plus")
                .messages(Arrays.asList(systemMsg, userMsg))
                .resultFormat(GenerationParam.ResultFormat.MESSAGE)
                .build();
        return gen.call(param);
    }

    public static void streamCall() throws NoApiKeyException, InputRequiredException {

        String bizParams =
                "{\"city\":\"杭州\"}";
        JSONObject jsonObject = new JSONObject();
        jsonObject.put("film_name", "长津湖");
        bizParams=jsonObject.toString();
        ApplicationParam param = ApplicationParam.builder()
                // 若没有配置环境变量，可用百炼API Key将下行替换为：api_key="sk-xxx"。但不建议在生产环境中直接将API Key硬编码到代码中，以减少API Key泄露风险。
//                .apiKey(System.getenv("DASHSCOPE_API_KEY"))
                .appId("717bf5c897ee4c0da2df32ded6180bce")
                .prompt("长津湖 要求字数500字左右")
                .incrementalOutput(true)
                .bizParams(JsonUtils.parse(bizParams))
                .build();

        Application application = new Application();
        Flowable<ApplicationResult> result = application.streamCall(param);
        result.blockingForEach(data -> {
            ApplicationOutput output = data.getOutput();
            System.out.printf("requestId: %s, text: %s, finishReason: %s\n",
                    data.getRequestId(), output.getText(), output.getFinishReason());//结束时 finishReason: stop
            String sessionId = output.getSessionId();
            System.out.printf("sessionId: %s\n", sessionId);
            ApplicationUsage usage = data.getUsage();
            List<ApplicationUsage.ModelUsage> models = usage.getModels();
            for (ApplicationUsage.ModelUsage model : models) {
                System.out.printf("modelid: %s, InputTokens: %d, getOutputTokens: %d\n",
                        model.getModelId(), model.getInputTokens(), model.getOutputTokens());
            }

        });
    }

    public static void assistantUsage() throws ApiException, NoApiKeyException, InputRequiredException, InvalidateParameter, InterruptedException {
//        Assistants assistants = new Assistants();
//        // build assistant parameters
//        AssistantParam param = AssistantParam.builder()
//                .model("qwen-max")
//                .name("intelligent guide")
//                .description("a smart guide")
//                .instructions("You are a helpful assistant.")
//                .build();
//        Assistant assistant = assistants.create(param);

        Assistants assistants = new Assistants();
        GeneralListParam listParam = GeneralListParam
                .builder()
                .limit(10l)
                .workspace("llm-vxbzv3j7z931qu6s")
                .build();
        ListResult<Assistant> listResult =  assistants.list(listParam);
        List<Assistant> data = listResult.getData();


        //指定workspace id


        Assistant assistant = assistants.retrieve("1aeea72cf8f7460e83476fe298d5f0a0");//llm-vxbzv3j7z931qu6s

        // create a thread
        Threads threads = new Threads();
        AssistantThread assistantThread = threads.create(ThreadParam.builder().build());
        // create a message to thread
        Messages messages = new Messages();
        ThreadMessage message = messages.create(assistantThread.getId(), TextMessageParam.builder().role("user").content("离开雷峰的日子").build());
        System.out.println(message);



        // create run
        Runs runs = new Runs();
        RunParam runParam = RunParam.builder().assistantId(assistant.getId()).stream(true).build();
//        RunParam runParam = RunParam.builder().assistantId("1aeea72cf8f7460e83476fe298d5f0a0").stream(true).build();
        Flowable<AssistantStreamMessage> runFlowable = runs.createStream(assistantThread.getId(), runParam);
        runFlowable.blockingForEach(assistantStreamMessage->{
            System.out.println("Event: " + assistantStreamMessage.getEvent());
            System.out.println("data: ");
            System.out.println(assistantStreamMessage.getData());
        });

        ListResult<ThreadMessage> threadMessages = messages.list(assistantThread.getId(), GeneralListParam.builder().build());
        System.out.println(threadMessages);
    }


}
